package com.example.contact;

import java.io.ByteArrayOutputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import android.content.ContentProviderOperation;
import android.content.ContentProviderOperation.Builder;
import android.content.ContentResolver;
import android.content.ContentUris;
import android.content.Context;
import android.content.OperationApplicationException;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.net.Uri;
import android.os.RemoteException;
import android.provider.ContactsContract;
import android.provider.ContactsContract.CommonDataKinds.Event;
import android.provider.MediaStore;
import android.text.TextUtils;
import android.util.Log;

import com.example.model.Contacts;
import com.example.util.Util;

public class ContactManager {

	private Context mContext;
	private Uri uri;
	private String selection;
	private String[] selectionArgs ;
	private String sortOrder;
	private ContentResolver cr;

	public ContactManager(Context mContext) {
		this.mContext = mContext;

		uri = ContactsContract.Contacts.CONTENT_URI;
		selection = ContactsContract.Contacts.IN_VISIBLE_GROUP + " = '" + ("1")
				+ "'";
		sortOrder = ContactsContract.Contacts.DISPLAY_NAME
				+ " COLLATE LOCALIZED ASC";
		cr = mContext.getContentResolver();
	}

	public HashMap<String,Contacts> getAllContact(String mEmail) {
		String id, email, phone, birthday, avarta = null, address;
		String[] name;
		int owner = 1;
		 HashMap<String,Contacts> list = null;
		try {
			list = new HashMap<String,Contacts>();

			Cursor cur = cr.query(uri, null, selection, selectionArgs,
					sortOrder);
			int size = cur.getCount();
			Log.e("ContactManager", "size: " + size);
			if (size > 0) {
				int cnt = 1;
				while (cur.moveToNext()) {
					email = "";
					cnt++;
					id = cur.getString(cur
							.getColumnIndex(ContactsContract.Contacts._ID));

					//Log.e("SON ID", "id: " + id);

					// name = cur
					// .getString(cur
					// .getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
					//
					// if (name != null && name != "") {
					// if (!Util.isEmailValid(name)) {
					// email = "";
					//
					// } else {
					// email = name;
					// name = email.substring(0, email.indexOf("@"));
					// }
					// }
					// firt - last name
					name = getName(cur, id);
					// phone
					phone = getPhone(cur, id);
					// email
					email = getEmail(id);
					// birthday
					birthday = getBirthday(id);
					// address
					address = getAddress(id);
					// photo
					Uri uri1 = getPhotoUri(id);
					if (uri1 != null)
						avarta = uri1.toString();

					// Log.e("SON", "id: " + id + " - name: " + name +
					// " - phone: " +
					// phone + " - email: " + email + " - birthday: " + birthday
					// + " - uri: " +
					// avarta);
					// if(name[0] == null && name[1] == null)
					// {
					// name[0] = email.substring(0, email.indexOf("@"));
					// name[1] = "";
					// }
					if (!TextUtils.isEmpty(email) && Util.isEmailValid(email) && !mEmail.equalsIgnoreCase(email)) {
						final Contacts c = new Contacts(name[0], name[1], id,
								email, birthday, phone, owner, avarta, address);
						c.setStatus(0);
						list.put(email, c);
					}
				}
			}
		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return list;
	}

	public String getAddress(String id) {
		String address = "";
		try {
			Uri postal_uri = ContactsContract.CommonDataKinds.StructuredPostal.CONTENT_URI;
			Cursor postal_cursor = cr.query(postal_uri, null,
					ContactsContract.Data.CONTACT_ID + "=" + id, null, null);
			while (postal_cursor.moveToNext()) {
				address = postal_cursor
						.getString(postal_cursor
								.getColumnIndex(ContactsContract.CommonDataKinds.StructuredPostal.STREET));
			}
			postal_cursor.close();
		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return address;
	}

	public String[] getName(Cursor cur, String id) {
		String[] name = null;
		try {
			name = new String[2];

			String whereName = ContactsContract.Data.MIMETYPE + " = ? and "
					+ ContactsContract.Data.CONTACT_ID + " = " + id;
			String[] whereNameParams = new String[] { ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE };
			Cursor nameCur = cr.query(ContactsContract.Data.CONTENT_URI, null,
					whereName, whereNameParams,
					ContactsContract.CommonDataKinds.StructuredName.GIVEN_NAME);
			nameCur.moveToNext();
			// while (nameCur.moveToNext()) {
			String given = nameCur
					.getString(nameCur
							.getColumnIndex(ContactsContract.CommonDataKinds.StructuredName.GIVEN_NAME));
			String family = nameCur
					.getString(nameCur
							.getColumnIndex(ContactsContract.CommonDataKinds.StructuredName.FAMILY_NAME));
			String display = nameCur
					.getString(nameCur
							.getColumnIndex(ContactsContract.CommonDataKinds.StructuredName.DISPLAY_NAME));
			//Log.e("SON", "Name: " + given + " Family: " + family
				//	+ " Displayname: " + display);

			name[0] = given;
			name[1] = family;
			// }
			nameCur.close();
		} catch (Exception ex) {

		}
		return name;
	}

	public String getPhone(Cursor cur, String id) {
		String phone = "";
		try {
			if (Integer
					.parseInt(cur.getString(cur
							.getColumnIndex(ContactsContract.Contacts.HAS_PHONE_NUMBER))) > 0)

			{
				Cursor pCur = cr.query(
						ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
						null, ContactsContract.CommonDataKinds.Phone.CONTACT_ID
								+ " = ?", new String[] { id }, null);

				while (pCur.moveToNext()) {
					String phonetype = pCur
							.getString(pCur
									.getColumnIndex(ContactsContract.CommonDataKinds.Phone.TYPE));
					String MainNumber = pCur
							.getString(pCur
									.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER));
					if (phonetype.equalsIgnoreCase("1")) {
						phone = MainNumber;
						break;
					} else if (phonetype.equalsIgnoreCase("2")) {
						phone = MainNumber;
						break;
					} else {
						phone = MainNumber;
						break;
					}
				}
				pCur.close();

			}
		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return phone;
	}

	public String getEmail(String id) {
		String email = "";
		try {
			Cursor emailCur = cr.query(
					ContactsContract.CommonDataKinds.Email.CONTENT_URI, null,
					ContactsContract.CommonDataKinds.Email.CONTACT_ID + " = ?",
					new String[] { id }, null);
			while (emailCur.moveToNext()) {

				email = emailCur
						.getString(emailCur
								.getColumnIndex(ContactsContract.CommonDataKinds.Email.DATA));
				String emailType = emailCur
						.getString(emailCur
								.getColumnIndex(ContactsContract.CommonDataKinds.Email.TYPE));

				if (email == null) {
					email = "unknown";
				}
				if (emailType.equalsIgnoreCase("1")) {
				} else {
				}
			}
			emailCur.close();
		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return email;
	}

	public String getBirthday(String id) {
		String birthday = "";
		try {
			String columns[] = {
					ContactsContract.CommonDataKinds.Event.START_DATE,
					ContactsContract.CommonDataKinds.Event.TYPE,
					ContactsContract.CommonDataKinds.Event.MIMETYPE, };

			String where = Event.TYPE + "=" + Event.TYPE_BIRTHDAY + " and "
					+ Event.MIMETYPE + " = '" + Event.CONTENT_ITEM_TYPE
					+ "' and " + ContactsContract.Data.CONTACT_ID + " = " + id;

			String[] selectionArgs = null;
			String sortOrder = ContactsContract.Contacts.DISPLAY_NAME;

			Cursor birthdayCur = cr.query(ContactsContract.Data.CONTENT_URI,
					columns, where, selectionArgs, sortOrder);
			if (birthdayCur.getCount() > 0) {
				while (birthdayCur.moveToNext()) {
					birthday = birthdayCur
							.getString(birthdayCur
									.getColumnIndex(ContactsContract.CommonDataKinds.Event.START_DATE));
				}
			}
			birthdayCur.close();
		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return birthday;
	}

	public Uri getPhotoUri(String id) {
		Cursor cur = null;
		try {
			cur = mContext
					.getContentResolver()
					.query(ContactsContract.Data.CONTENT_URI,
							null,
							ContactsContract.Data.CONTACT_ID
									+ "="
									+ id
									+ " AND "
									+ ContactsContract.Data.MIMETYPE
									+ "='"
									+ ContactsContract.CommonDataKinds.Photo.CONTENT_ITEM_TYPE
									+ "'", null, null);
			if (cur != null) {
				if (!cur.moveToFirst()) {
					return null; // no photo
				}
			} else {
				return null; // error in cursor process
			}
			Uri person = ContentUris.withAppendedId(
					ContactsContract.Contacts.CONTENT_URI, Long.parseLong(id));
			return Uri.withAppendedPath(person,
					ContactsContract.Contacts.Photo.CONTENT_DIRECTORY);
		} catch (Exception e) {

			return null;
		} finally {
			if (cur != null)
				cur.close();
		}

	}

	public void createContact(String firstname, String lastname, String phone,
			String email, String address) {

		// Cursor cur = cr.query(uri, null, selection, selectionArgs,
		// sortOrder);

		// if (cur.getCount() > 0) {
		// while (cur.moveToNext()) {
		// String existName =
		// cur.getString(cur.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME));
		// if (existName.contains(email)) {
		// Log.e("SON", "The contact name: " + email + " already exists");
		// return;
		// }
		// }
		// }

		ArrayList<ContentProviderOperation> ops = new ArrayList<ContentProviderOperation>();
		ops.add(ContentProviderOperation
				.newInsert(ContactsContract.RawContacts.CONTENT_URI)
				.withValue(ContactsContract.RawContacts.ACCOUNT_TYPE, null)// "accountname@gmail.com")
				.withValue(ContactsContract.RawContacts.ACCOUNT_NAME, null)// "com.google")
				.build());
		if (firstname != null) {
			ops.add(ContentProviderOperation
					.newInsert(ContactsContract.Data.CONTENT_URI)
					.withValueBackReference(
							ContactsContract.Data.RAW_CONTACT_ID, 0)
					.withValue(
							ContactsContract.Data.MIMETYPE,
							ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE)
					.withValue(
							ContactsContract.CommonDataKinds.StructuredName.GIVEN_NAME,
							firstname).build());
		}
		if (lastname != null) {
			ops.add(ContentProviderOperation
					.newInsert(ContactsContract.Data.CONTENT_URI)
					.withValueBackReference(
							ContactsContract.Data.RAW_CONTACT_ID, 0)
					.withValue(
							ContactsContract.Data.MIMETYPE,
							ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE)
					.withValue(
							ContactsContract.CommonDataKinds.StructuredName.FAMILY_NAME,
							lastname).build());
		}
		// ops.add(ContentProviderOperation.newInsert(ContactsContract.Data.CONTENT_URI)
		// .withValueBackReference(ContactsContract.Data.RAW_CONTACT_ID, 0)
		// .withValue(ContactsContract.Data.MIMETYPE,
		// ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE)
		// .withValue(ContactsContract.CommonDataKinds.StructuredName.DISPLAY_NAME,
		// firstname + " " + lastname)
		// .build());
		if (phone != null) {
			ops.add(ContentProviderOperation
					.newInsert(ContactsContract.Data.CONTENT_URI)
					.withValueBackReference(
							ContactsContract.Data.RAW_CONTACT_ID, 0)
					.withValue(
							ContactsContract.Data.MIMETYPE,
							ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE)
					.withValue(ContactsContract.CommonDataKinds.Phone.NUMBER,
							phone)
					.withValue(ContactsContract.CommonDataKinds.Phone.TYPE,
							ContactsContract.CommonDataKinds.Phone.TYPE_HOME)
					.build());
		}
		if (email != null) {
			ops.add(ContentProviderOperation
					.newInsert(ContactsContract.Data.CONTENT_URI)
					.withValueBackReference(
							ContactsContract.Data.RAW_CONTACT_ID, 0)
					.withValue(
							ContactsContract.Data.MIMETYPE,
							ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE)
					.withValue(ContactsContract.CommonDataKinds.Email.DATA,
							email)
					.withValue(ContactsContract.CommonDataKinds.Email.TYPE,
							ContactsContract.CommonDataKinds.Email.TYPE_HOME)
					.build());
		}
		if (address != null) {
			ops.add(ContentProviderOperation
					.newInsert(ContactsContract.Data.CONTENT_URI)
					.withValueBackReference(
							ContactsContract.Data.RAW_CONTACT_ID, 0)
					.withValue(
							ContactsContract.Data.MIMETYPE,
							ContactsContract.CommonDataKinds.StructuredPostal.CONTENT_ITEM_TYPE)
					.withValue(
							ContactsContract.CommonDataKinds.StructuredPostal.STREET,
							address)
					.withValue(
							ContactsContract.CommonDataKinds.StructuredPostal.TYPE,
							ContactsContract.CommonDataKinds.StructuredPostal.TYPE_HOME)
					.build());
		}

		try {
			cr.applyBatch(ContactsContract.AUTHORITY, ops);
		} catch (RemoteException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (OperationApplicationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		// Toast.makeText(NativeContentProvider.this,
		// "Created a new contact with name: " + name + " and Phone No: " +
		// phone, Toast.LENGTH_SHORT).show();

	}

	public void deleteAlContact() {
		ContentResolver cr = mContext.getContentResolver();
		Cursor cur = cr.query(ContactsContract.Contacts.CONTENT_URI, null,
				null, null, null);
		while (cur.moveToNext()) {
			try {
				String lookupKey = cur.getString(cur
						.getColumnIndex(ContactsContract.Contacts.LOOKUP_KEY));
				Uri uri = Uri
						.withAppendedPath(
								ContactsContract.Contacts.CONTENT_LOOKUP_URI,
								lookupKey);
				System.out.println("The uri is " + uri.toString());
				cr.delete(uri, null, null);
			} catch (Exception e) {
				System.out.println(e.toString());
			}
		}
	}

	public void update(String id, String firstname, String lastname,
			String phone, String email, String address, String photo) {
		ArrayList<ContentProviderOperation> ops = new ArrayList<ContentProviderOperation>();

		// Name
		Builder builder = ContentProviderOperation
				.newUpdate(ContactsContract.Data.CONTENT_URI);
		builder.withSelection(
				ContactsContract.Data.CONTACT_ID + "=?" + " AND "
						+ ContactsContract.Data.MIMETYPE + "=?",
				new String[] {
						String.valueOf(id),
						ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE });
		builder.withValue(
				ContactsContract.CommonDataKinds.StructuredName.FAMILY_NAME,
				lastname);
		builder.withValue(
				ContactsContract.CommonDataKinds.StructuredName.GIVEN_NAME,
				firstname);
		ops.add(builder.build());

		// Number
		builder = ContentProviderOperation
				.newUpdate(ContactsContract.Data.CONTENT_URI);
		builder.withSelection(
				ContactsContract.Data.CONTACT_ID + "=?" + " AND "
						+ ContactsContract.Data.MIMETYPE + "=?" + " AND "
						+ ContactsContract.CommonDataKinds.Organization.TYPE
						+ "=?",
				new String[] {
						String.valueOf(id),
						ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE,
						String.valueOf(ContactsContract.CommonDataKinds.Phone.TYPE_HOME) });
		builder.withValue(ContactsContract.CommonDataKinds.Phone.NUMBER, phone);
		ops.add(builder.build());

		// Email
		builder = ContentProviderOperation
				.newUpdate(ContactsContract.Data.CONTENT_URI);
		builder.withSelection(
				ContactsContract.Data.CONTACT_ID + "=?" + " AND "
						+ ContactsContract.Data.MIMETYPE + "=?" + " AND "
						+ ContactsContract.CommonDataKinds.Organization.TYPE
						+ "=?",
				new String[] {
						String.valueOf(id),
						ContactsContract.CommonDataKinds.Email.CONTENT_ITEM_TYPE,
						String.valueOf(ContactsContract.CommonDataKinds.Email.TYPE_HOME) });
		builder.withValue(ContactsContract.CommonDataKinds.Email.DATA, email);
		ops.add(builder.build());
		// Address
		builder = ContentProviderOperation
				.newUpdate(ContactsContract.Data.CONTENT_URI);
		builder.withSelection(
				ContactsContract.Data.CONTACT_ID + "=?" + " AND "
						+ ContactsContract.Data.MIMETYPE + "=?" + " AND "
						+ ContactsContract.CommonDataKinds.Organization.TYPE
						+ "=?",
				new String[] {
						String.valueOf(id),
						ContactsContract.CommonDataKinds.StructuredPostal.CONTENT_ITEM_TYPE,
						String.valueOf(ContactsContract.CommonDataKinds.StructuredPostal.TYPE_HOME) });
		builder.withValue(ContactsContract.CommonDataKinds.Email.DATA, address);
		ops.add(builder.build());
		// Picture
		try {
			Bitmap bitmap = MediaStore.Images.Media.getBitmap(cr,
					Uri.parse(photo));
			ByteArrayOutputStream image = new ByteArrayOutputStream();
			bitmap.compress(Bitmap.CompressFormat.JPEG, 100, image);

			builder = ContentProviderOperation
					.newUpdate(ContactsContract.Data.CONTENT_URI);
			builder.withSelection(
					ContactsContract.Data.CONTACT_ID + "=?" + " AND "
							+ ContactsContract.Data.MIMETYPE + "=?",
					new String[] {
							String.valueOf(id),
							ContactsContract.CommonDataKinds.Photo.CONTENT_ITEM_TYPE });
			builder.withValue(ContactsContract.CommonDataKinds.Photo.PHOTO,
					image.toByteArray());
			ops.add(builder.build());
		} catch (Exception e) {
			e.printStackTrace();
		}

		// Update
		try {
			mContext.getContentResolver().applyBatch(
					ContactsContract.AUTHORITY, ops);
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	private void deleteContact(String id) {

		String where = ContactsContract.Data.CONTACT_ID + " = ? ";
		String[] params = new String[] { id };

		ArrayList<ContentProviderOperation> ops = new ArrayList<ContentProviderOperation>();
		ops.add(ContentProviderOperation
				.newDelete(ContactsContract.RawContacts.CONTENT_URI)
				.withSelection(where, params).build());
		try {
			cr.applyBatch(ContactsContract.AUTHORITY, ops);
		} catch (RemoteException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (OperationApplicationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}

		// Toast.makeText(NativeContentProvider.this,
		// "Deleted the contact with name '" + name +"'",
		// Toast.LENGTH_SHORT).show();

	}
}
